package com.yl.wzy.banner;

import android.annotation.SuppressLint;
import android.content.Context;
import android.graphics.Color;
import android.os.Build;
import android.os.Handler;
import android.os.Message;
import android.support.annotation.RequiresApi;
import android.support.v4.view.ViewPager;
import android.text.TextUtils;
import android.util.AttributeSet;
import android.util.Log;
import android.view.Gravity;
import android.view.View;
import android.view.ViewGroup;
import android.webkit.MimeTypeMap;
import android.widget.FrameLayout;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.RelativeLayout;
import android.widget.TextView;

import com.bumptech.glide.Glide;
import com.maning.mnvideoplayerlibrary.player.YLVideoPlayer;
import com.yl.wzy.R;

import java.util.ArrayList;
import java.util.List;

/**
 * 视频 + 图片 混合banner
 *
 * @author wzy
 */

public class YLBanner extends RelativeLayout {

    private ViewPager viewPager;
    private final int UPTATE_VIEWPAGER = 100;
    //  图片默认时间间隔
    private int imgDelayed = 2000;
    //  每个位置默认时间间隔，因为有视频的原因
    private int delayedTime = 2000;
    //  默认显示位置
    private int autoCurrIndex = 0;
    //  是否自动播放
    private boolean isAutoPlay = false;
    private Time time;
    private List<BannerModel> bannerModels;
    private List<String> mData;
    private List<View> views;
    private BannerViewAdapter mAdapter;

    private int containsVideoCount;

    private TextView indicatorVideo;    //  视频指示器
    private TextView indicatorImage;    //  图片指示器
    private TextView indicatorImageNumber;  //  图片指示器(具体位置/数量)

    private final String videoFormat = "mp4";
    private List<String> imageList;

    public YLBanner(Context context) {
        super(context);
        init();
    }

    public YLBanner(Context context, AttributeSet attrs) {
        super(context, attrs);
        init();
    }

    public YLBanner(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        init();
    }

    @RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
    public YLBanner(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
        super(context, attrs, defStyleAttr, defStyleRes);
        init();
    }

    private void init() {
        time = new Time();
        viewPager = new ViewPager(getContext());
        ViewGroup.LayoutParams vp_param = new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);
        viewPager.setLayoutParams(vp_param);

        this.addView(viewPager);
    }

    /**
     * 源
     *
     * @param dataList    视频+图片
     * @param placeholder 视频占位
     */
    public void setDataList(List<String> dataList, String placeholder) {

        if (dataList == null) {
            dataList = new ArrayList<>();
        }

        for (int i = 0; i < dataList.size(); i++) {
            String data = dataList.get(i);

            if (TextUtils.isEmpty(data))    //  容错
            {
                dataList.remove(i);
                continue;
            }

            if (data.endsWith(videoFormat))   //  包含视频
            {
                containsVideoCount++;
            }
        }
        mData = dataList;

        initIndicator();

        initImageIndicator(dataList);

        //  用于显示的数组
        if (views == null) {
            views = new ArrayList<>();
        } else {
            views.clear();
        }

        FrameLayout.LayoutParams paramsVideo = new FrameLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);

        int screenWidth = getResources().getDisplayMetrics().widthPixels;
        paramsVideo.width = screenWidth;
        paramsVideo.height = screenWidth * 9 / 16;
        paramsVideo.gravity = Gravity.CENTER_VERTICAL;

        //  数据大于一条，才可以循环
        if (dataList.size() > 1) {
            autoCurrIndex = 1;
            //  循环数组，将首位各加一条数据
            for (int i = 0; i < dataList.size() + 2; i++) {
                String url;
                if (i == 0) {
                    url = dataList.get(dataList.size() - 1);
                } else if (i == dataList.size() + 1) {
                    url = dataList.get(0);
                } else {
                    url = dataList.get(i - 1);
                }

                if (MimeTypeMap.getFileExtensionFromUrl(url).equals(videoFormat)) {

                    FrameLayout frameLayout = new FrameLayout(getContext());
                    frameLayout.setLayoutParams(params);

                    YLVideoPlayer videoPlayer = new YLVideoPlayer(getContext());
                    videoPlayer.setLayoutParams(paramsVideo);
                    videoPlayer.setDataSource(url, placeholder);

                    frameLayout.addView(videoPlayer);
                    views.add(frameLayout);

                } else {
                    ImageView imageView = new ImageView(getContext());
                    imageView.setLayoutParams(params);
                    imageView.setScaleType(ImageView.ScaleType.CENTER_CROP);
                    Glide.with(getContext()).load(url).centerCrop().into(imageView);
                    views.add(imageView);
                }
            }
        } else if (dataList.size() == 1) {
            autoCurrIndex = 0;
            String url = dataList.get(0);
            if (MimeTypeMap.getFileExtensionFromUrl(url).equals(videoFormat)) {

                FrameLayout frameLayout = new FrameLayout(getContext());
                frameLayout.setLayoutParams(params);

                YLVideoPlayer videoPlayer = new YLVideoPlayer(getContext());
                videoPlayer.setLayoutParams(paramsVideo);
                videoPlayer.setDataSource(MimeTypeMap.getFileExtensionFromUrl(url), placeholder);

                frameLayout.addView(videoPlayer);
                views.add(videoPlayer);
            } else {
                ImageView imageView = new ImageView(getContext());
                imageView.setLayoutParams(params);
                imageView.setScaleType(ImageView.ScaleType.CENTER_CROP);
                Glide.with(getContext()).load(url).centerCrop().into(imageView);
                views.add(imageView);
            }
        }
    }

    /**
     * 图片指示器
     *
     * @param dataList 数据源
     */
    @SuppressLint("DefaultLocale")
    private void initImageIndicator(List<String> dataList) {
        imageList = new ArrayList<>();
        if (dataList == null || dataList.size() <= 0) return;

        for (int i = 0; i < dataList.size(); i++) {

            if (TextUtils.isEmpty(dataList.get(i))) //  容错
            {
                dataList.remove(i);
                continue;
            }

            if (!dataList.get(i).endsWith(videoFormat))  //  不是视频就添加到图片集合中
            {
                imageList.add(dataList.get(i));
            }
        }
        indicatorImageNumber = new TextView(getContext());
        RelativeLayout.LayoutParams layoutParams = new RelativeLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        layoutParams.addRule(RelativeLayout.ALIGN_PARENT_BOTTOM);
        layoutParams.addRule(RelativeLayout.ALIGN_PARENT_END);
        layoutParams.rightMargin = 20;
        layoutParams.bottomMargin = 50;
        indicatorImageNumber.setLayoutParams(layoutParams);

        indicatorImageNumber.setText(String.format("1/%d", imageList.size()));
        indicatorImageNumber.setTextColor(Color.WHITE);
        indicatorImageNumber.setTextSize(12.0f);
        indicatorImageNumber.setBackgroundResource(R.drawable.corner_round_oval_transgray);
        indicatorImageNumber.setPadding(18, 5, 18, 5);
        this.addView(indicatorImageNumber);
        indicatorImageNumber.setVisibility(GONE);   //  默认不显示
    }

    /**
     * 显示指示器
     */
    private void initIndicator() {
        if (containsVideoCount <= 0) return;   //  没有视频资源 则不显示

        RelativeLayout.LayoutParams layoutParams = new RelativeLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        LinearLayout linearLayout = new LinearLayout(getContext());

        layoutParams.addRule(RelativeLayout.CENTER_HORIZONTAL);
        layoutParams.addRule(RelativeLayout.ALIGN_PARENT_BOTTOM);

        layoutParams.bottomMargin = 50;
        linearLayout.setOrientation(LinearLayout.HORIZONTAL);
        linearLayout.setLayoutParams(layoutParams);

        indicatorVideo = new TextView(getContext());
        LinearLayout.LayoutParams videoParams = new LinearLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        videoParams.rightMargin = 10;
        indicatorVideo.setLayoutParams(videoParams);
        indicatorVideo.setText("视频");
        indicatorVideo.setTextColor(Color.WHITE);
        indicatorVideo.setTextSize(12.0f);
        indicatorVideo.setBackgroundResource(R.drawable.corner_round_oval_theme_btn);
        indicatorVideo.setPadding(12, 5, 12, 5);
        linearLayout.addView(indicatorVideo);

        indicatorImage = new TextView(getContext());
        LinearLayout.LayoutParams imageParams = new LinearLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        imageParams.leftMargin = 10;
        indicatorImage.setLayoutParams(imageParams);
        indicatorImage.setText("图片");
        indicatorImage.setTextColor(Color.WHITE);
        indicatorImage.setTextSize(12.0f);
        indicatorImage.setBackgroundResource(R.drawable.corner_round_oval_theme_btn);
        indicatorImage.setPadding(12, 5, 12, 5);
        linearLayout.addView(indicatorImage);

        this.addView(linearLayout);

        indicatorVideo.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View v) {
                for (int i = 0; i < mData.size(); i++) {
                    if (mData.get(i).endsWith(videoFormat)) //  第一个视频源索引
                    {
                        try {
                            viewPager.setCurrentItem(i + 1);
                        } catch (Exception e)    //  防止角标越界
                        {
                            viewPager.setCurrentItem(0);
                        }
                        break;
                    }
                }
            }
        });
        indicatorImage.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View v) {
                for (int i = 0; i < mData.size(); i++) {
                    if (!mData.get(i).endsWith(videoFormat)) //  第一个图片源索引
                    {
                        try {
                            viewPager.setCurrentItem(i + 1);
                        } catch (Exception e)    //  防止角标越界
                        {
                            viewPager.setCurrentItem(0);
                        }
                        break;
                    }
                }
            }
        });

    }


    public void setImgDelayed(int imgDelayed) {
        this.imgDelayed = imgDelayed;
    }

    public void startBanner() {
        if (views == null || views.size() <= 0) return;

        mAdapter = new BannerViewAdapter(views);
        viewPager.setAdapter(mAdapter);

        viewPager.setOffscreenPageLimit(views.size() > 1 ? views.size() : 1);   //  预加载全部 （会验证占用内存，但无限轮播时video不会被销毁）
        viewPager.setCurrentItem(autoCurrIndex);
        viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
            @SuppressLint("DefaultLocale")
            @Override
            public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
                //  页面刚打开时执行
                if (containsVideoCount <= 0 || (indicatorVideo == null | indicatorImage == null))
                    return;

                if (containsVideoCount >= position)    //  当前正处于视频item 视频选择器设置颜色，图片选择器设置灰色
                {
                    indicatorImageNumber.setVisibility(GONE);
                    indicatorVideo.setBackgroundResource(R.drawable.corner_round_oval_theme_btn);
                    indicatorImage.setBackgroundResource(R.drawable.corner_round_oval_gray);
                } else   //   图片item  反之；显示图片指示数量
                {
                    indicatorVideo.setBackgroundResource(R.drawable.corner_round_oval_gray);
                    indicatorImage.setBackgroundResource(R.drawable.corner_round_oval_theme_btn);

                    if (position - containsVideoCount > imageList.size())   //  不符合实际情况
                    {
                        indicatorImageNumber.setVisibility(GONE);
                        return;
                    }
                    indicatorImageNumber.setVisibility(VISIBLE);
                    indicatorImageNumber.setText(String.format("%d/%d", position - containsVideoCount, imageList.size()));
                }
            }

            @Override
            public void onPageSelected(int position) {
                Log.d("TAG", autoCurrIndex + "onPageSelected position:" + position);

                View view = views.get(autoCurrIndex);
                if (view instanceof FrameLayout)  //  关闭上一个视频源
                {
                    try {
                        if (((FrameLayout) view).getChildCount() < 1) return;
                        YLVideoPlayer videoView = (YLVideoPlayer) ((FrameLayout) view).getChildAt(0);
                        videoView.pauseVideo();
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }
                //  当前位置
                autoCurrIndex = position;
                getDelayedTime(position);
            }

            @Override
            public void onPageScrollStateChanged(int state) {

                //  移除自动计时
                mHandler.removeCallbacks(runnable);

                //  ViewPager跳转
                int pageIndex = autoCurrIndex;
                if (autoCurrIndex == 0) {
                    pageIndex = views.size() - 2;
                } else if (autoCurrIndex == views.size() - 1) {
                    pageIndex = 1;
                }
                if (pageIndex != autoCurrIndex)  //  无滑动动画，直接跳转
                {
                    viewPager.setCurrentItem(pageIndex, false);
                }

                if (state == 0 && isAutoPlay && views.size() > 1)   //  停止滑动时，重新自动倒计时
                {
                    View view1 = views.get(pageIndex);
                    if (view1 instanceof FrameLayout) {
                        try {
                            if (((FrameLayout) view1).getChildCount() < 1) return;
                            final YLVideoPlayer videoPlayer = (YLVideoPlayer) ((FrameLayout) view1).getChildAt(0);
                            int current = videoPlayer.getVideoCurrentPosition();
                            int duration = videoPlayer.getVideoTotalDuration();
                            delayedTime = duration - current;
                            //  某些时候，某些视频，获取的时间无效，就延时10秒，重新获取
                            if (delayedTime <= 0) {
                                time.getSurplusTime(videoPlayer, runnable);
                                mHandler.postDelayed(time, imgDelayed);
                            } else {
                                mHandler.postDelayed(runnable, delayedTime);
                            }
                        } catch (Exception e) {
                            e.printStackTrace();
                        }

                    } else {
                        delayedTime = imgDelayed;
                        mHandler.postDelayed(runnable, delayedTime);
                    }
                    Log.d("TAG", "onPageScrollStateChanged--->" + pageIndex + "--" + autoCurrIndex);
                }
            }
        });
    }

    //开启自动循环
    public void startAutoPlay() {
        isAutoPlay = true;
        if (views.size() > 1) {
            getDelayedTime(autoCurrIndex);
            if (delayedTime <= 0) {
                mHandler.postDelayed(time, imgDelayed);
            } else {
                mHandler.postDelayed(runnable, delayedTime);
            }
        }
    }

    /**
     * 发消息，进行循环
     */
    private Runnable runnable = new Runnable() {
        @Override
        public void run() {
            mHandler.sendEmptyMessage(UPTATE_VIEWPAGER);
        }
    };

    /**
     * 获取视频长度，以及已经播放的时间
     */
    private class Time implements Runnable {

        private YLVideoPlayer videoView;
        private Runnable runnable;

        void getSurplusTime(YLVideoPlayer videoView, Runnable runnable) {
            this.videoView = videoView;
            this.runnable = runnable;
        }

        @Override
        public void run() {
            int current = videoView.getVideoCurrentPosition();
            int duration = videoView.getVideoTotalDuration();
            int surplusTime = duration - current;
            mHandler.postDelayed(runnable, surplusTime);
        }
    }

    //接受消息实现轮播
    @SuppressLint("HandlerLeak")
    private Handler mHandler = new Handler() {
        public void handleMessage(Message msg) {
            switch (msg.what) {
                case UPTATE_VIEWPAGER:
                    viewPager.setCurrentItem(autoCurrIndex + 1, false);
                    break;
            }
        }
    };

    private class BannerModel {
        public String url;
        public int playTime;
        public int type = 0;
    }

    /**
     * 获取delyedTime
     *
     * @param position 当前位置
     */
    private void getDelayedTime(int position) {
        View view1 = views.get(position);
        if (view1 instanceof FrameLayout) {
            try {
                if (((FrameLayout) view1).getChildCount() < 1) return;
                YLVideoPlayer videoPlayer = (YLVideoPlayer) view1;
//            videoPlayer.startVideo();
                delayedTime = videoPlayer.getVideoCurrentPosition();
                time.getSurplusTime(videoPlayer, runnable);
            } catch (Exception e) {
                e.printStackTrace();
            }

        } else {
            delayedTime = imgDelayed;
        }
    }

    public void dataChange(List<String> list, String placeholder) {
        if (list != null && list.size() > 0) {
            //  改变资源时要重新开启循环，否则会把视频的时长赋给图片，或者相反
            //  因为delyedTime也要改变，所以要重新获取delyedTime
            mHandler.removeCallbacks(runnable);
            setDataList(list, placeholder);
            mAdapter.setDataList(views);
            mAdapter.notifyDataSetChanged();
            viewPager.setCurrentItem(autoCurrIndex, false);
            //开启循环
            if (isAutoPlay && views.size() > 1) {
                getDelayedTime(autoCurrIndex);
                if (delayedTime <= 0) {
                    mHandler.postDelayed(time, imgDelayed);
                } else {
                    mHandler.postDelayed(runnable, delayedTime);
                }
            }
        }
    }

    public void destroy() {
        mHandler.removeCallbacksAndMessages(null);
        mHandler = null;
        time = null;
        runnable = null;
        views.clear();
        views = null;
        viewPager = null;
        mAdapter = null;
    }
}
